#pragma once
#include <unistd.h>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <pthread.h>
#include <list>
#include <assert.h>
#include <exception>
#include "locker.hpp"

#define MAX_REQUEST_NUMBER 1024

void addEvent(int epfd, int sock, bool epolloneshot);

template <class T>
class threadPool
{
public:
    threadPool(int thread_number = 8, int max_request_number = 1000) : thread_num(thread_number), 
    max_request_num(max_request_number), stop(false), tid(NULL)
    {
        if (thread_number <= 0 || max_request_number <= 0)
        {
            throw exception();
        }
        tid = new pthread_t[thread_num];
        assert(tid);
        for (int i = 0;i < thread_num;i++)
        {
            //创建线程
            if (pthread_create(&tid[i], NULL, work, this) != 0)
            {
                delete[] tid;
                throw exception();
            }
            //分离线程
            if (pthread_detach(tid[i]))
            {
                delete[] tid;
                throw exception();
            }
        }
    }

    ~threadPool()
    {
        delete[] tid;
        stop = true;
    }

    bool append(T* request)
    {
        printf("有新的请求到达\n");
        lck.lock();
        if (work_queue.size() > MAX_REQUEST_NUMBER)
        {
            lck.unlock();
            return false;
        }
        work_queue.push_back(request);
        lck.unlock();
        sem.post();
        return true;
    }

    static void* work(void* arg)
    {
        threadPool<T>* tp = (threadPool<T>*)arg;
        tp->run();
        return tp;
    }

    void run()
    {
        while (!stop)
        {
            sem.wait();
            lck.lock();
            if (work_queue.empty())
            {
                lck.unlock();
                continue;
            }
            T* request = work_queue.front();
            work_queue.pop_front();
            lck.unlock();
            if (request == NULL)
                continue;
            printf("该线程获取到请求\n");
            request->process();
        }
    }
private:
    //最多能执行的请求数量
    int max_request_num;
    //线程数量
    int thread_num;
    //工作队列
    list<T*> work_queue;
    //互斥锁
    Locker lck;
    //信号量
    Sem sem;
    //运行开关
    bool stop;
    //线程数组
    pthread_t* tid;
};